﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

/*
* University of Reykjavík
* Brjóstagjöf.is is the product of first-year practical programming course
* for computer science students at said university
*
* URL: http://code.google.com/p/scags 
* Authors: 
* Ástvaldur Sigurðsson
* Guðjón Jónsson
* Kristín Inga Vigfúsdóttir
* Steinar Bragi Sigurðsson
* Sveinn Ernstsson
*/
namespace skags.Models
{
    /*
    * Samskipti við töflur Articles og ArticleCategory í gagnagrunni
    */
    public class ArticleRepository : IDataRepository
    {
        // tilvik af gagnagrunni (vísun/tenging í gagnagrunn) búin til
        DBDataContext dc = new DBDataContext();

        // Vistar breytingar
        public void Save()
        {
            dc.SubmitChanges();
        }

        /* 
         * Hækkar færsluna ReadCount i gagnagrunni fyrir tiltekna grein (articelItem)
         * ReadCount segir til um hve oft grein hefur verið sótt í gagnagrunn 
         */
        public void UpdateReadCount(Article articleItem)
        {
            if (articleItem.ReadCount != null)
            {
                articleItem.ReadCount += 1;
            }
            else
            {
                articleItem.ReadCount = 1;
            }
            Save(); // 
        }

        /* 
         * Naer í allar greinar og alla flokka 
         * Einungis notað í ArticleController
         */
        public ArticleTablesViewModel GetAll(int limit)
        {
            var allArticle = (from s in dc.Articles
                          where s.Approved == true
                          orderby s.ID descending
                          select s).Take(limit);

            // Köllum á fall sem sér um að skera meginmál greinanna niður
            foreach (var s in allArticle)
                s.Text = DBRepository.LimitWords(s.Text, "/Article/ViewItem/" + s.ID);

            var allCategories = from s in dc.ArticleCategories
                                orderby s.Title ascending
                                select s;

            return new ArticleTablesViewModel { Article = allArticle, Categories = allCategories };
        }

        /* 
         * Skilar öllum greinum
         * Notað í AdminController og MockDataContext fyrir prófanir
         */
        public IEnumerable<ArticleViewModel> GetAllArticles()
        {
            var result = from a in dc.Articles
                         join c in dc.ArticleCategories on a.CategoryID equals c.ID
                         join u in dc.aspnet_Users on a.CreatorID equals u.UserId
                         orderby a.Approved, a.ID descending
                         select new ArticleViewModel
                         {
                             ID = a.ID,
                             Title = a.Title,
                             CreatorID = a.CreatorID,
                             CreatorName = u.UserName,
                             DateCreated = a.DateCreated,
                             Text = a.Text,
                             ReadCount = a.ReadCount,
                             Tags = a.Tags,
                             CategoryID = a.CategoryID,
                             CategoryName = c.Title,
                             Approved = a.Approved
                         };

            return result;
        }
        /*
         * Skilar öllum flokkum
         * Notað í Admin- og ProfileController, líka í MockDataContext fyrir einingaprufanir.
         */
        public IEnumerable<ArticleCategory> GetAllCategories()
        {
            var result = from s in dc.ArticleCategories
                         orderby s.ID descending
                         select s;

            return result;
        }

        /*
         * Skilar greinum eftir flokkanúmeri.
         * Notað í MockDataContext fyrir einingaprófanir og ArticleController.
         */
        public ArticleTablesViewModel GetArticlesByCategoryID(int id)
        {
            var allCategories = from s in dc.ArticleCategories
                                orderby s.Title ascending
                                select s;

            var allArticles = from s in dc.Articles
                          where s.CategoryID == id && s.Approved == true
                          orderby s.ID descending
                          select s;

            // Köllum á fall sem sér um að skera meginmál greinanna niður
            foreach (var s in allArticles)
                s.Text = DBRepository.LimitWords(s.Text, "/Article/ViewItem/" + s.ID);

            return new ArticleTablesViewModel { Article = allArticles, Categories = allCategories };
        }

        /*
         * Skilar grein eftir númeri
         * Einungis notað af ArticleController 
         */ 
        public Article GetArticleByID(int id)
        {
            return dc.Articles.SingleOrDefault(u => u.ID == id);
        }

        public IEnumerable<ArticleViewModel> GetNewestByAmount(int amount)
        {
            UserRepository urep = new UserRepository();

            return (from n in dc.Articles
                    where n.Approved == true
                    orderby n.DateCreated descending
                    select new ArticleViewModel
                    {
                        ID = n.ID,
                        CategoryID = n.CategoryID,
                        CategoryName = n.ArticleCategory.Title,
                        CreatorID = n.CreatorID,
                        CreatorName = urep.GetNameByHashID(n.CreatorID),
                        DateCreated = n.DateCreated,
                        ReadCount = n.ReadCount,
                        Tags = n.Tags,
                        Text = n.Text,
                        Title = n.Title,

                    }).Take(amount);
        }

        public IEnumerable<ArticleViewModel> GetMostReadByAmount(int amount)
        {
            UserRepository urep = new UserRepository();

            return (from n in dc.Articles
                    where n.Approved == true
                    orderby n.ReadCount descending
                    select new ArticleViewModel
                    {
                        ID = n.ID,
                        CategoryID = n.CategoryID,
                        CategoryName = n.ArticleCategory.Title,
                        CreatorID = n.CreatorID,
                        CreatorName = urep.GetNameByHashID(n.CreatorID),
                        DateCreated = n.DateCreated,
                        ReadCount = n.ReadCount,
                        Tags = n.Tags,
                        Text = n.Text,
                        Title = n.Title,

                    }).Take(amount);
        }

        public ArticleCatViewModel GetArticleCatByID(int id)
        {
            var theArticle = dc.Articles.SingleOrDefault(u => u.ID == id);
            var allCategories = GetAllCategories();

            return new ArticleCatViewModel
            {
                ID = theArticle.ID,
                Title = theArticle.Title,
                CreatorID = theArticle.CreatorID,
                DateCreated = theArticle.DateCreated,
                Text = theArticle.Text,
                ReadCount = theArticle.ReadCount,
                Tags = theArticle.Tags,
                CategoryID = theArticle.CategoryID,
                Approved = theArticle.Approved,
                Categories = allCategories
            };
        }

        /*
         * Skilar flokki greinar eftir númeri
         * Einungis notað af AdminController
         */
        public ArticleCategory GetArticleCategoryByID(int id)
        {
            return (from s in dc.ArticleCategories
                    where s.ID == id
                    select s).SingleOrDefault();
        }

        /*
         * Uppfaerir grein
         * Einungis notað af AdminController
         */ 
        public void UpdateArticle(Article item)
        {
            var theArticle = GetArticleByID(item.ID);
            if (theArticle != null)
            {
                theArticle.CategoryID = item.CategoryID;
                theArticle.ReadCount = item.ReadCount;
                theArticle.Tags = item.Tags;
                theArticle.Text = item.Text;
                theArticle.Title = item.Title;
                theArticle.Approved = item.Approved;

                Save();
            }
        }

        /*
         * Uppfaerir flokk
         * Einungis notað af AdminController
         */
        public void UpdateArticleCategory(ArticleCategory item)
        {
            var theCat = GetArticleCategoryByID(item.ID);
            if (theCat != null)
            {
                theCat.Title = item.Title;
            }

            Save();
        }

        /*
         * Baetir við grein.
         * Notað af baeði Admin- og ProfileController.
         * Útfaert í baeði ArticleControllerTest og MockDataContext fyrir einingaprufanir.
         */ 
        public void AddArticle(Article item)
        {
            dc.Articles.InsertOnSubmit(item);
            Save();
            EmailLogMedia mailman = new EmailLogMedia();
            mailman.SendSubscriptionUpdate();
        }

        /* 
         * Baetir við flokki.
         * Notað af AdminController.
         * Útfaert í ArticleControllerTest og MockDataContext fyrir einingaprófanir.
         */
        public void AddArticleCategory(ArticleCategory item)
        {
            dc.ArticleCategories.InsertOnSubmit(item);
            Save();
        }

        /*
         * Eyða grein.
         * Einungis notað í AdminController.
         */ 
        public void DeleteArticle(int id)
        {
            var itemToDelete = GetArticleByID(id);

            dc.Articles.DeleteOnSubmit(itemToDelete);

            Save();
        }

        /* 
         * Eyðir greinaflokk og öllum hans greinum
         * Einungis notað í AdminController
         */
        public void DeleteArticleCategory(int id)
        {
            // Finnum allar greinar í þessum flokk
            var articleToDelete = from s in dc.Articles
                               where s.CategoryID == id
                               select s;
            // Finnum færsluna í gagnagrunninum
            var catToDelete = GetArticleCategoryByID(id);

            dc.Articles.DeleteAllOnSubmit(articleToDelete);
            dc.ArticleCategories.DeleteOnSubmit(catToDelete);

            Save();
        }
    }
}